#pragma once 
#include "sock.hpp"
#include "common.hpp"
#include "addr.hpp"
#include <unistd.h>
#include <algorithm>
#include <sys/epoll.h>

class Epoll
{

public:
    Epoll()
    {
        int n = epoll_create(128);
        if (n < 0)
        {
            use_log(loglevel::DEBUG) << "epoll_create fail!";
            exit(EPOLL_FAIL);
        }
        else
        {
            use_log(loglevel::DEBUG) << "epoll_create success!";

            _epollfd = n;
        }
    }

    void event_operate(int oper, int fd, int event)
    {
        struct epoll_event ev;
        ev.events = event;
        ev.data.fd = fd;
        int n = epoll_ctl(_epollfd, oper, fd, &ev);
        if (n < 0)
        {
            use_log(loglevel::DEBUG) << "epoll_ctl fail!";
            return;
        }
        use_log(loglevel::DEBUG) << "epoll_ctl sucess!";
    }
    void Addevent(int fd, int event)
    {
        event_operate(EPOLL_CTL_ADD, fd, event);
    }
    void Delevent(int fd, int event)
    {
        event_operate(EPOLL_CTL_DEL, fd, event);
    }
    void Modevent(int fd, int event)
    {
        event_operate(EPOLL_CTL_MOD, fd, event);
    }

    int Waitevent(struct epoll_event evs[128], int maxnum, int timeout)
    {
        int n = epoll_wait(_epollfd, evs, maxnum, timeout);
        if (n < 0)
            use_log(loglevel::DEBUG) << "epoll_wait fail!";
        else if (n == 0)
            use_log(loglevel::DEBUG) << "epoll_wait timeout!";

        else
            use_log(loglevel::DEBUG) << "epoll_wait sucess!";

             

        return n;
    }

    ~Epoll()
    {

        if (_epollfd > 0)
            close(_epollfd);
    }

private:
    int _epollfd;
};